home *** CD-ROM | disk | FTP | other *** search
/ C/C++ Users Group Library 1996 July / C-C++ Users Group Library July 1996.iso / vol_400 / 414_02 / portable / wgetch.c < prev    next >
Encoding:
C/C++ Source or Header  |  1993-06-17  |  5.0 KB  |  206 lines

  1. #define    CURSES_LIBRARY    1
  2. #include <curses.h>
  3. #undef    wgetch
  4.  
  5. #ifdef PDCDEBUG
  6. char *rcsid_wgetch = "$Header: C:\CURSES\portable\RCS\wgetch.c 2.1 1993/06/18 20:19:01 MH Rel MH $";
  7. #endif
  8.  
  9. static WINDOW *w;            /* to reduce stack usage   */
  10.  
  11.  
  12.  
  13.  
  14.  
  15.  
  16.  
  17. /*man-start*********************************************************************
  18.  
  19.   wgetch()    - read character
  20.  
  21.   X/Open Description:
  22.      A character is read from the terminal associated with the
  23.      window.  In nodelay mode, if there is no input waiting,
  24.      the value ERR is returned.  In delay mode, the program will
  25.      hang until the system passes text through to the program.
  26.      Depending on the setting of cbreak(), this will be after one
  27.      character or after the first newline.  Unless noecho() has
  28.      been set, the character will also be echoed into the designated
  29.      window.
  30.  
  31.      If keypad() is TRUE, and a function key is pressed, the token for
  32.      that function key will be returned instead of the raw characters.
  33.      Possible function keys are defined in <curses.h> with integers
  34.      beginning with 0401, whose names begin with KEY_.  If a character
  35.      is received that could be the beginning of a function key (such as
  36.      escape), curses will set a timer.  If the remainder of the sequence
  37.      does not come in within the designated time, the character will be
  38.      passed through, otherwise the function key value will be returned.
  39.      For this reason, on many terminals, there will be a delay after a
  40.      user presses the escape key before the escape is returned to the
  41.      program.  (Use by a programmer of the escape key for a single
  42.      character function is discouraged.)
  43.  
  44.      If nodelay(win,TRUE) has been called on the window and no input is
  45.      waiting, the value ERR is returned.
  46.  
  47.      NOTE: getch(), mvgetch() and mvwgetch() are macros.
  48.  
  49.   PDCurses Description:
  50.      Given the nature of the PC, there is no such timer set for an
  51.      incoming ESCAPE value, because function keys generate unique
  52.      scan codes that are not prefixed with the ESCAPE character.
  53.  
  54.      Also, note that the getch() definition will conflict  with
  55.      many DOS compiler's runtime libraries.
  56.  
  57.   X/Open Return Value:
  58.      This functions return ERR or the value of the character, meta 
  59.      character or function key token.
  60.  
  61.   PDCurses Errors:
  62.      It is an error to call this function with a NULL window pointer.
  63.  
  64.   Portability:
  65.      PDCurses    int wgetch( WINDOW* win );
  66.      X/Open Dec '88    int wgetch( WINDOW* win );
  67.      BSD Curses    int wgetch( WINDOW* win );
  68.      SYS V Curses    int wgetch( WINDOW* win );
  69.  
  70. **man-end**********************************************************************/
  71.  
  72. int    wgetch(WINDOW *win)
  73. {
  74. extern    short    c_pindex;        /* putter index           */
  75. extern    short    c_gindex;        /* getter index           */
  76. extern    short    c_ungind;        /* wungetch() push index   */
  77. extern    chtype    c_ungch[NUNGETCH];    /* array of ungotten chars */
  78. extern  WINDOW*    _getch_win_;
  79.  
  80.     signed    key;
  81.     bool    cbr;
  82.     static    chtype    buffer[_INBUFSIZ];    /* character buffer */
  83. #ifdef UNIX
  84.     short display_key = 0400;
  85.     bool cbreak_set = FALSE;
  86. #else
  87.     short display_key = 0x100;
  88. #endif
  89.  
  90. #ifdef PDCDEBUG
  91.     if (trace_on) PDC_debug("wgetch() - called\n");
  92. #endif
  93.  
  94.     if (win == (WINDOW *)NULL)
  95.         return( ERR );
  96.  
  97.     if (c_ungind)                /* if ungotten char exists */
  98.         return( c_ungch[--c_ungind] );    /* remove and return it */
  99.  
  100.     if (win->_nodelay
  101.     && !PDC_check_bios_key())
  102.         return(ERR);
  103.  
  104.     _getch_win_ = win;
  105.  
  106.     if ((!_cursvar.raw_inp) &&
  107.         (!_cursvar.cbreak))
  108.     {
  109.         /*
  110.          * if normal
  111.          */
  112.         if (c_gindex < c_pindex)
  113.         {
  114.             /*
  115.              * and data in buffer
  116.              */
  117.             return( buffer[c_gindex++] );
  118.         }
  119.     }
  120.  
  121.     w = win;        /* static for speed & stack */
  122.     c_pindex = 0;        /* prepare to buffer data */
  123.     c_gindex = 0;
  124.     for(;;)            /* loop for any buffering */
  125.     {
  126. #ifdef UNIX
  127.         if (!(_cursvar.raw_inp || _cursvar.cbreak))
  128.             {
  129.             cbreak();
  130.             cbreak_set = TRUE;
  131.             }
  132.         if (w->_use_keypad)
  133.             key = PDC_sysgetch();
  134.         else
  135.             key = PDC_rawgetch();
  136.         if (cbreak_set)
  137.             nocbreak();
  138. #else
  139.         if (_cursvar.raw_inp)
  140.         {
  141.             /*
  142.              * get a raw character
  143.              */
  144.             key = PDC_rawgetch();
  145.         }
  146.         else
  147.         {
  148.             /*
  149.              * get a system character
  150.              * if break return proper
  151.              */
  152.             cbr = PDC_get_ctrl_break();
  153.             PDC_set_ctrl_break(_cursvar.orgcbr);
  154.             key = PDC_sysgetch();
  155.             PDC_set_ctrl_break(cbr);    /* restore as it was */
  156.         }
  157. #endif
  158.         if (w->_nodelay && (key == -1))
  159.         {
  160.             /*
  161.              * if nodelay and no char
  162.              */
  163.             return( ERR );
  164.         }
  165.         if ((key == '\r') &&
  166.             (_cursvar.autocr) &&
  167.             (!_cursvar.raw_inp))
  168.         {
  169.             /*
  170.              * translate CR
  171.              */
  172.             key = '\n';
  173.         }
  174.         if (_cursvar.echo && (key < display_key))
  175.         {
  176.             /*
  177.              * if echo is enabled
  178.              */
  179.             waddch(w, key);
  180.             wrefresh(w);
  181.         }
  182.         if (_cursvar.raw_inp || _cursvar.cbreak)
  183.         {
  184.             /*
  185.              * if no buffering
  186.              */
  187.             return( key );
  188.         }
  189.  
  190.         if (c_pindex < _INBUFSIZ - 2)
  191.         {
  192.             /*
  193.              * if no overflow, put data in buffer
  194.              */
  195.             buffer[c_pindex++] = key;
  196.         }
  197.         if ((key == '\n') || (key == '\r'))
  198.         {
  199.             /*
  200.              * if we got a line
  201.              */
  202.             return( buffer[c_gindex++] );
  203.         }
  204.     }
  205. }
  206.